package org.agilelang.db.generator;

/*
 AgileLang - A fourth generation language(http://www.agilelang.org).

 Copyright (C) 2013 Roderick Cusirramos (roderick20@hotmail.com)

 This program is free software; you can redistribute it and/or modify
 it under the terms of the GNU General Public License as published by
 the Free Software Foundation; either version 2 of the License, or
 (at your option) any later version.

 This program is distributed in the hope that it will be useful,
 but WITHOUT ANY WARRANTY; without even the implied warranty of
 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 GNU General Public License for more details.

 You should have received a copy of the GNU General Public License
 along with this program; if not, write to the Free Software
 Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
 */

import java.io.*;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.Statement;
import java.util.HashMap;
import java.util.List;
import org.agilelang.mvc.Generator;
import org.agilelang.object.Model;
import org.agilelang.object.attributes.Attribute;
import org.agilelang.object.attributes.Reference;

public class GMySql extends Generator{

    String nameDB;
    String user;
    String pass;
    boolean createDB = false;
    String TAB = "\t";//tab
    String BR = "\n";//Salto de liena
    String iniTable = "CREATE TABLE ";
    String endTable = "PRIMARY KEY (`id`) )ENGINE=INNODB;";
    String primaryKey = "`id` int(11) unsigned NOT NULL auto_increment,";
    String PRIMARY_KEY = "";
    String FOREIGN_KEY = "";
    String FIELD = "";
    HashMap data = new HashMap();
    String reference_str = "";
    String fileSql = "";

    public GMySql() {
        super();
        data.put("binary", "blob");
        data.put("boolean", "tinyint(1)");
        data.put("date", "date");
        data.put("datetime", "datetime");
        data.put("decimal", "decimal");
        data.put("float", "float");
        data.put("double", "double");
        data.put("integer", "int(11)");
        data.put("string", "varchar(255)");
        data.put("text", "text");
        data.put("enum", "int");
        data.put("time", "time");
        data.put("timestamp", "datetime");
        data.put("primary key", "`id` int(11) unsigned NOT NULL auto_increment");
        data.put("int", "int(11)");
    }

    public void setModelList(List<Model> list) {

        int tm = list.size();
        for (int i = 0; i < tm; i++) {
            String table = "";
            String atrr = "";
            Model model = list.get(i);
            List<Attribute> attrs = model.attributes;
            int ta = attrs.size();
            for (int j = 0; j < ta; j++) {
                Attribute attr = attrs.get(j);//
                if(attr.name.endsWith("_id")){
                    atrr = atrr + TAB + "`" + attr.name + "` " + data.get(attr.type) + " unsigned NOT NULL," + BR;
                }else{
                    atrr = atrr + TAB + "`" + attr.name + "` " + data.get(attr.type) + "," + BR;
                }
                    
                
            }

            if (!model.table.equals("")) {
                table = "DROP TABLE IF EXISTS `" + model.table + "`;" + BR
                        + iniTable + model.table + "(" + BR
                        + TAB + primaryKey + BR
                        + atrr
                        + TAB + endTable + BR + BR;

                List<Reference> references = model.references;
                ta = references.size();
                for (int j = 0; j < ta; j++) {
                    Reference reference = references.get(j);
                    reference_str = reference_str
                            + "ALTER TABLE `" + model.table  + "` ADD FOREIGN KEY (`" + reference.foreign_key.toLowerCase() + "`) REFERENCES `" + this.setPluralize(reference.model_reference.toLowerCase()) + "` (`id`);" + BR;
                }
            } else {
                table = "DROP TABLE IF EXISTS `" + model.name.toLowerCase() + "`;" + BR
                        + iniTable + model.name.toLowerCase() + "(" + BR
                        + TAB + primaryKey + BR
                        + atrr
                        + TAB + endTable + BR + BR;

                List<Reference> references = model.references;
                ta = references.size();
                for (int j = 0; j < ta; j++) {
                    Reference reference = references.get(j);
                    reference_str = reference_str
                            + "ALTER TABLE `" + model.name.toLowerCase() + "` ADD FOREIGN KEY (`" + reference.foreign_key.toLowerCase() + "`) REFERENCES `" + reference.model_reference.toLowerCase() + "` (`id`);" + BR;
                }
            }



            fileSql = fileSql + table;
        }
    }

    public String getFileSql() {
        return fileSql + reference_str;
    }

    public void writeFileSql(String path) {
        createfile("mysql_script.sql", path, fileSql + reference_str);
    }

    public void setDB(String mySQL) {
    }

    public void setConectionParams(String namedb, String user, String pass) {
        this.nameDB = namedb;
        this.user = user;
        this.pass = pass;
    }

    public void createDB() {
        Connection connection = null;
        Statement statement = null;
        String sql = "";
        try {
            Class.forName("com.mysql.jdbc.Driver").newInstance();
            String url = "jdbc:mysql://localhost/";//; + this.nameDB;
            connection = DriverManager.getConnection(url, this.user, this.pass);

            if (this.createDB == true) {//crear
                statement = connection.createStatement();
                sql = "DROP DATABASE IF EXISTS `" + this.nameDB + "`";
                statement.executeUpdate(sql);

                sql = "CREATE DATABASE " + this.nameDB;
                statement.executeUpdate(sql);

                statement = connection.createStatement();
                sql = "USE " + this.nameDB;
                statement.executeUpdate(sql);


            } else {//utilizar
                statement = connection.createStatement();
                sql = "USE " + this.nameDB;
                statement.executeUpdate(sql);
            }


            String[] state = fileSql.split(";");
            for (int i = 0; i < state.length - 1; i++) {
                System.out.println(state[i]);
                statement.executeUpdate(state[i]);
            }

        } catch (Exception e) {
            e.printStackTrace();
        }
    }

    protected void createfile(String Name, String path, String Contenido) {
        Writer output = null;
        System.out.println(path + File.separator + Name);
        File file = new File(path + File.separator + Name);
        try {
            output = new BufferedWriter(new FileWriter(file));
            output.write(Contenido);
            output.close();
        } catch (IOException ex) {
            System.out.println(ex.toString());
        }
    }
}
